package io.github.xxyopen.novel.service.impl;

import io.github.xxyopen.novel.core.common.constant.ErrorCodeEnum;
import io.github.xxyopen.novel.core.common.resp.PageRespDto;
import io.github.xxyopen.novel.core.common.resp.RestResp;
import io.github.xxyopen.novel.core.constant.StuBehaviorConstant;
import io.github.xxyopen.novel.dao.entity.*;
import io.github.xxyopen.novel.dao.mapper.*;
import io.github.xxyopen.novel.service.PracticeService;
import org.checkerframework.checker.units.qual.A;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Service
public class PracticeServiceImpl implements PracticeService {

    @Autowired
    private PracticeMapper practiceMapper;

    @Autowired
    private SysUserMapper sysUserMapper;

    @Autowired
    private SysDeptMapper sysDeptMapper;

    @Autowired
    private PracticeCommentMapper practiceCommentMapper;

    @Autowired
    private StuBehaviorMapper stuBehaviorMapper;

    @Autowired
    private StuPracticeMapper stuPracticeMapper;

    @Autowired
    private StuTeacherMapper stuTeacherMapper;

    @Override
    public List<Practice> getListSlider() {
        return practiceMapper.getPracticeSlider();
    }

    @Override
    public RestResp<Practice> getPracticeById(Integer id) {
        if (id == null) {
            return RestResp.ok(null);
        }
        Practice practice = practiceMapper.getPracticeById(id);
        // 根据id查询作者信息
        SysUser authorInfo = sysUserMapper.getUserById(practice.getCreateBy());
        // 获取部门信息
        SysDept childDept = sysDeptMapper.getDeptById(authorInfo.getDeptId());
        SysDept fatherDept = sysDeptMapper.getDeptById(Long.valueOf(childDept.getAncestors().split(",")[2]));
        authorInfo.setDeptName(fatherDept.getDeptName() + "-" + childDept.getDeptName());
        practice.setAuthorInfo(authorInfo);
        return RestResp.ok(practice);
    }

    @Override
    public RestResp addComment(PracticeComment practiceComment) {
        Long userId = practiceComment.getUserId();
        if (userId == null) {
            return RestResp.fail(ErrorCodeEnum.REQUIRED_LOGIN);
        }
        int i = practiceCommentMapper.insertComment(practiceComment);
        // 添加学生行为
        if (i > 0) {
            StuBehavior stuBehavior = new StuBehavior();
            stuBehavior.setStuId(userId);
            stuBehavior.setPracticeId(practiceComment.getPracticeId());
            stuBehavior.setAction(StuBehaviorConstant.COMMENT);
            stuBehaviorMapper.insertStuBehavior(stuBehavior);
        }
        // 添加评论数
        practiceMapper.incrCommentCount(practiceComment.getPracticeId());
        return RestResp.ok(null);
    }

    @Override
    public RestResp<PageRespDto<PracticeComment>> getComments(Long practiceId, Integer pageNum, Integer pageSize) {
        List<PracticeComment> comments = practiceCommentMapper.selectCommentsByPracticeId(practiceId);
        // 计算分页的起始和结束索引
        int startIndex = (pageNum - 1) * pageSize;
        int endIndex = Math.min(pageNum * pageSize, comments.size());  // 防止超出总数

        // 截取分页数据
        List<PracticeComment> pagedComments = comments.subList(startIndex, endIndex);

        return RestResp.ok(PageRespDto.of(pageNum, pageSize, comments.size(),
                pagedComments));
    }

    @Override
    public void clickPractice(StuBehavior stuBehavior) {
        if (stuBehavior.getStuId() == null) {
            return;
        }
        stuBehavior.setAction(StuBehaviorConstant.CLICK);
        // 记录学生点击行为
        stuBehaviorMapper.insertStuBehavior(stuBehavior);
        // 增加点击量
        practiceMapper.incrClickCount(stuBehavior.getPracticeId());
    }

    @Override
    public RestResp singUpPractice(StuPractice stuPractice) {
        Practice practice = practiceMapper.getPracticeById(Math.toIntExact(stuPractice.getPracticeId()));
        // 是否已报名
        StuPractice stuPrac = stuPracticeMapper.getStuPractice(stuPractice);
        if (stuPrac != null) {
            return RestResp.ok("已报名");
        }
        // 报名已截止
        if(LocalDateTime.now().isAfter(practice.getSignupDeadline())){
            return RestResp.ok("已截止报名");
        }
        // 实践已满人
        if (practice.getMaxEnrollCount() == practice.getRealEnrollCount()){
            return RestResp.ok("实践已满人");
        }
        // 添加学生实践关系
        int i = stuPracticeMapper.insertStuPractice(stuPractice);
        // 增加实际报名人数
        if(i > 0) {
            practiceMapper.incrRealEnrollCount(stuPractice.getPracticeId());
        }
        // 添加学生-教师关系
        StuTeacher stuTeacher = new StuTeacher();
        stuTeacher.setStuId(stuPractice.getStuId());
        stuTeacher.setTeacherId(practice.getCreateBy());
        stuTeacherMapper.insertStuTeacher(stuTeacher);
        return RestResp.ok(null);
    }

    @Override
    public RestResp getPracticeStatus(Long stuId, Long practiceId) {
        Map<String, Object> map = new HashMap<>();
        map.put("practiceStatusCode", 0);
        Practice practice = practiceMapper.getPracticeById(Math.toIntExact(practiceId));
        // 是否已报名
        StuPractice stuPractice = new StuPractice();
        stuPractice.setStuId(stuId);
        stuPractice.setPracticeId(practiceId);
        StuPractice stuPrac = stuPracticeMapper.getStuPractice(stuPractice);
        if (stuPrac != null) {
            map.put("practiceStatusCode", 1);
            map.put("practiceStatus", "已报名");
        }
        // 报名已截止
        if(LocalDateTime.now().isAfter(practice.getSignupDeadline())){
            map.put("practiceStatusCode", 1);
            map.put("practiceStatus", "已截止报名");
        }
        // 实践已满人
        if (practice.getMaxEnrollCount() == practice.getRealEnrollCount()){
            map.put("practiceStatusCode", 1);
            map.put("practiceStatus", "实践已满人");
        }
        // 点赞状态
        StuBehavior like = stuBehaviorMapper.selectByAction(stuId, practiceId, StuBehaviorConstant.LIKE);
        map.put("like", like == null ? false : true);
        // 收藏状态
        StuBehavior collect = stuBehaviorMapper.selectByAction(stuId, practiceId, StuBehaviorConstant.COLLECT);
        map.put("collect", collect == null ? false : true);
        return RestResp.ok(map);
    }

    @Override
    public void updatePractice(Practice practice) {
        practiceMapper.updatePractice(practice);
    }

    @Override
    public void likeOrCollectPractice(StuBehavior stuBehavior) {
        if (stuBehavior.getInsertOrDelete() == 1) {
            stuBehaviorMapper.insertStuBehavior(stuBehavior);
        }else {
            stuBehaviorMapper.deleteStuBehavior(stuBehavior);
        }
    }

    @Override
    public RestResp getMySignUpPractice(Long stuId, Integer pageNum, Integer pageSize) {
        List<StuPractice> practices = stuPracticeMapper.getMySignUpPractice(stuId);
        // 计算分页的起始和结束索引
        int startIndex = (pageNum - 1) * pageSize;
        int endIndex = Math.min(pageNum * pageSize, practices.size());  // 防止超出总数

        // 截取分页数据
        List<StuPractice> pagedComments = practices.subList(startIndex, endIndex);

        return RestResp.ok(PageRespDto.of(pageNum, pageSize, practices.size(),
                pagedComments));
    }

    @Override
    public RestResp getMyCollection(Long stuId, Integer pageNum, Integer pageSize) {
        List<StuPractice> practices = stuPracticeMapper.getMyCollection(stuId);
        // 计算分页的起始和结束索引
        int startIndex = (pageNum - 1) * pageSize;
        int endIndex = Math.min(pageNum * pageSize, practices.size());  // 防止超出总数

        // 截取分页数据
        List<StuPractice> pagedComments = practices.subList(startIndex, endIndex);

        return RestResp.ok(PageRespDto.of(pageNum, pageSize, practices.size(),
                pagedComments));
    }

    @Override
    public RestResp getRecentPublish() {
        List<Practice> practices = practiceMapper.getRecentPublish();
        return RestResp.ok(practices);
    }

    @Override
    public RestResp getThisWeekHot() {
        return RestResp.ok(practiceMapper.getThisWeekHot());
    }

    @Override
    public RestResp getRecentDeadline() {
        return RestResp.ok(practiceMapper.getRecentDeadline());
    }

    @Override
    public RestResp getClickRank() {
        return RestResp.ok(practiceMapper.getClickRank());
    }

    @Override
    public RestResp searchPractice(Integer pageNum, Integer pageSize, String key, String sort) {
        if(key == null){
            key = "";
        }
        if(sort == null || "".equals(sort)){
            sort = "order by create_time desc";
        }else {
            sort = "order by " + sort;
        }
        List<Practice> practices = practiceMapper.searchPractice(key, sort);

        int startIndex = (pageNum - 1) * pageSize;
        int endIndex = Math.min(pageNum * pageSize, practices.size());

        List<Practice> practiceList = practices.subList(startIndex, endIndex);

        return RestResp.ok(PageRespDto.of(pageNum, pageSize, practices.size(),
                practiceList));
    }
}
